package org.example.springoauth2.securitycommon.config.authenticate;

import lombok.AllArgsConstructor;
import org.example.springoauth2.securitycommon.config.authenticate.handler.*;
import org.example.springoauth2.securitycommon.service.SysUserService;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.builders.WebSecurity;
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
import org.springframework.security.web.authentication.AuthenticationSuccessHandler;

/**
 * @author hzq
 * @date 2021/9/11 16:31
 */
@Configuration
@AllArgsConstructor
public class WebSecurityAuthorizationConfiguration extends WebSecurityConfigurerAdapter {

    private final SysUserService sysUserService;
    private final CustomizeAuthenticationFailureHandler customizeAuthenticationFailureHandler;
    private final CustomizeAuthenticationSuccessHandler customizeAuthenticationSuccessHandler;
    private final FormAuthenticationFailureHandler formAuthenticationFailureHandler;
    private final SsoLogoutSuccessHandler ssoLogoutSuccessHandler;

    @Override
    protected void configure(HttpSecurity http) throws Exception {
        // 由于循环依赖 AuthenticationManager 这里使用new的方式构建自定配置
        CustomizeAuthorizationSecurityConfig customizeAuthorizationSecurityConfig = new CustomizeAuthorizationSecurityConfig(
                sysUserService,
                customizeAuthenticationFailureHandler,
                customizeAuthenticationSuccessHandler,
                authenticationManagerBean());
        http.apply(customizeAuthorizationSecurityConfig)
                .and()
                .formLogin().loginPage("/token/login").loginProcessingUrl("/token/form").failureHandler(formAuthenticationFailureHandler)
                .successHandler(tenantSavedRequestAwareAuthenticationSuccessHandler())
                .and()
                .logout().logoutSuccessHandler(ssoLogoutSuccessHandler).deleteCookies("JSESSIONID").invalidateHttpSession(true)
                .and()
                .authorizeRequests().antMatchers("/token/**", "/actuator/**").permitAll().anyRequest().authenticated()
                .and()
                .csrf().disable();
    }

    @Override
    public void configure(WebSecurity web) throws Exception {
        web.ignoring().antMatchers("/css/**");
    }

    @Bean
    @Override
    public AuthenticationManager authenticationManagerBean() throws Exception {
        return super.authenticationManagerBean();
    }

    @Bean
    public AuthenticationSuccessHandler tenantSavedRequestAwareAuthenticationSuccessHandler() {
        return new TenantSavedRequestAwareAuthenticationSuccessHandler();
    }
}
